Skip to content

Addfinal specifier to the classop #145977

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Jun 30, 2025
Merged

Conversation

Jaddyen
Copy link
Contributor

@Jaddyen Jaddyen commented Jun 26, 2025

In some use cases of the ClassOp, eg MLGO, we would like to be able to declare the class as final. This specifier allows for that.

@@ -1,6 +1,6 @@
// RUN: mlir-translate --mlir-to-cpp %s | FileCheck %s

emitc.class @modelClass {
emitc.class final @modelClass {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd add a separate test for final. Otherwise lgtm

@Jaddyen Jaddyen marked this pull request as ready for review June 26, 2025 22:16
@llvmbot
Copy link
Member

llvmbot commented Jun 26, 2025

@llvm/pr-subscribers-mlir-emitc

@llvm/pr-subscribers-mlir

Author: Jaden Angella (Jaddyen)

Changes

In some use cases of the ClassOp, eg MLGO, we would like to be able to declare the class as final. This specifier allows for that.


Full diff: https://github.com/llvm/llvm-project/pull/145977.diff

3 Files Affected:

  • (modified) mlir/include/mlir/Dialect/EmitC/IR/EmitC.td (+13-2)
  • (modified) mlir/lib/Target/Cpp/TranslateToCpp.cpp (+4-2)
  • (modified) mlir/test/mlir-translate/emitc_classops.mlir (+27-2)
diff --git a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
index 91ee89919e58e..7fe2da8f7e044 100644
--- a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
+++ b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
@@ -1618,10 +1618,20 @@ def EmitC_ClassOp
         return
       }
     }
+    // Class with a final speciferAdd commentMore actions
+    emitc.class final @modelClass {
+      emitc.field @fieldName0 : !emitc.array<1xf32> = {emitc.opaque = "input_tensor"}
+      emitc.func @execute() {
+        %0 = "emitc.constant"() <{value = 0 : index}> : () -> !emitc.size_t
+        %1 = get_field @fieldName0 : !emitc.array<1xf32>
+        %2 = subscript %1[%0] : (!emitc.array<1xf32>, !emitc.size_t) -> !emitc.lvalue<f32>
+        return
+      }
+    }
     ```
   }];
 
-  let arguments = (ins SymbolNameAttr:$sym_name);
+  let arguments = (ins SymbolNameAttr:$sym_name, UnitAttr:$final_specifier);
 
   let regions = (region AnyRegion:$body);
 
@@ -1632,7 +1642,8 @@ def EmitC_ClassOp
 
   let hasCustomAssemblyFormat = 1;
 
-  let assemblyFormat = [{ $sym_name attr-dict-with-keyword $body }];
+  let assemblyFormat =
+      [{ (`final` $final_specifier^)? $sym_name attr-dict-with-keyword $body }];
 }
 
 def EmitC_FieldOp : EmitC_Op<"field", [Symbol]> {
diff --git a/mlir/lib/Target/Cpp/TranslateToCpp.cpp b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
index c04548688bcf6..ab91b32d7ef43 100644
--- a/mlir/lib/Target/Cpp/TranslateToCpp.cpp
+++ b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
@@ -1000,8 +1000,10 @@ static LogicalResult printOperation(CppEmitter &emitter, ModuleOp moduleOp) {
 static LogicalResult printOperation(CppEmitter &emitter, ClassOp classOp) {
   CppEmitter::Scope classScope(emitter);
   raw_indented_ostream &os = emitter.ostream();
-  os << "class " << classOp.getSymName() << " {\n";
-  os << "public:\n";
+  os << "class " << classOp.getSymName();
+  if (classOp.getFinalSpecifier())
+    os << " final";
+  os << " {\n public:\n";
   os.indent();
 
   for (Operation &op : classOp) {
diff --git a/mlir/test/mlir-translate/emitc_classops.mlir b/mlir/test/mlir-translate/emitc_classops.mlir
index e42844412860e..adaf79313868e 100644
--- a/mlir/test/mlir-translate/emitc_classops.mlir
+++ b/mlir/test/mlir-translate/emitc_classops.mlir
@@ -1,4 +1,4 @@
-// RUN: mlir-translate --mlir-to-cpp %s | FileCheck %s
+// RUN: mlir-translate --mlir-to-cpp -split-input-file %s | FileCheck %s
 
 emitc.class @modelClass {
     emitc.field @fieldName0 : !emitc.array<1xf32> 
@@ -12,7 +12,32 @@ emitc.class @modelClass {
     }
 }
 
-// CHECK: class modelClass {
+// CHECK-LABEL: class modelClass {
+// CHECK-NEXT: public:
+// CHECK-NEXT:  float[1] fieldName0;
+// CHECK-NEXT:  float[1] fieldName1;
+// CHECK-NEXT:  void execute() {
+// CHECK-NEXT:    size_t v1 = 0;
+// CHECK-NEXT:    float[1] v2 = fieldName0;
+// CHECK-NEXT:    float[1] v3 = fieldName1;
+// CHECK-NEXT:    return;
+// CHECK-NEXT:  }
+// CHECK-EMPTY:
+// CHECK-NEXT: };
+
+emitc.class final @finalClass {
+    emitc.field @fieldName0 : !emitc.array<1xf32> 
+    emitc.field @fieldName1 : !emitc.array<1xf32> 
+    emitc.func @execute() {
+        %0 = "emitc.constant"() <{value = 0 : index}> : () -> !emitc.size_t
+        %1 = get_field @fieldName0 : !emitc.array<1xf32>
+        %2 = get_field @fieldName1 : !emitc.array<1xf32>
+        %3 = subscript %1[%0] : (!emitc.array<1xf32>, !emitc.size_t) -> !emitc.lvalue<f32>
+        return
+    }
+}
+
+// CHECK-LABEL: class finalClass final {
 // CHECK-NEXT: public:
 // CHECK-NEXT:  float[1] fieldName0;
 // CHECK-NEXT:  float[1] fieldName1;

@@ -1,4 +1,4 @@
// RUN: mlir-translate --mlir-to-cpp %s | FileCheck %s
// RUN: mlir-translate --mlir-to-cpp -split-input-file %s | FileCheck %s
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why do you need to split-input-file?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i dont!
thanks for pointing this out.

Copy link
Member

mtrofin commented Jun 30, 2025

Merge activity

  • Jun 30, 1:18 AM UTC: A user started a stack merge that includes this pull request via Graphite.
  • Jun 30, 1:19 AM UTC: Graphite couldn't merge this PR because it failed for an unknown reason (Stack merges are not currently supported for forked repositories. Please create a branch in the target repository in order to merge).

@mtrofin mtrofin merged commit d4b5905 into llvm:main Jun 30, 2025
7 checks passed
@Jaddyen Jaddyen deleted the add-classop-specifier branch June 30, 2025 15:28
rlavaee pushed a commit to rlavaee/llvm-project that referenced this pull request Jul 1, 2025
In some use cases of the `ClassOp`, eg MLGO, we would like to be able to declare the class as final. This specifier allows for that.
rlavaee pushed a commit to rlavaee/llvm-project that referenced this pull request Jul 1, 2025
In some use cases of the `ClassOp`, eg MLGO, we would like to be able to declare the class as final. This specifier allows for that.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants